package com.jrx.anytxn.transaction.service.impl;

import com.jrx.anytxn.common.exception.TxnBizException;
import com.jrx.anytxn.customer.entity.CmCustomerSecondLevel;
import com.jrx.anytxn.customer.mapper.ext.ExtCmCustomerSecondLevelMapper;
import com.jrx.anytxn.param.entity.TlFilePaymentLog;
import com.jrx.anytxn.param.service.system.IOrganizationTableService;
import com.jrx.anytxn.ribbon.config.GrayVersionConfig;
import com.jrx.anytxn.transaction.bean.DebtBean;
import com.jrx.anytxn.transaction.bean.FilePaymentSaveBean;
import com.jrx.anytxn.transaction.bean.PayoffProveMessage;
import com.jrx.anytxn.transaction.constant.TransBizConstant;
import com.jrx.anytxn.transaction.entity.AmLoanAccountInfo;
import com.jrx.anytxn.transaction.entity.AmLoanMainInfo;
import com.jrx.anytxn.transaction.entity.TlMistakeLog;
import com.jrx.anytxn.transaction.entity.TlThirdPartyPayment;
import com.jrx.anytxn.transaction.handler.IPaymentHandler;
import com.jrx.anytxn.transaction.mapper.ext.ExtAmLoanAccountInfoMapper;
import com.jrx.anytxn.transaction.mapper.ext.ExtTlThirdPartyPaymentMapper;
import com.jrx.anytxn.transaction.service.IDebtCalculationService;
import com.jrx.anytxn.transaction.service.IFilePayService;
import com.jrx.anytxn.transaction.service.IMistakeService;
import com.jrx.anytxn.transaction.service.IThirdPartyPaymentService;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.math.BigDecimal;
import java.util.Date;

/**
 * @program: anytxn-cf-parent
 * @description: 处理文件还款实现类
 * @author: xiaoyu.jing
 * @date: 2021-03-10 16:58
 **/
@Service
public class FilePayServiceImpl implements IFilePayService {

    Logger logger = LoggerFactory.getLogger(FilePayServiceImpl.class);

    @Resource
    private ExtAmLoanAccountInfoMapper extAmLoanAccountInfoMapper;
    @Autowired
    private IDebtCalculationService debtCalculationService;
    @Autowired
    private IOrganizationTableService organizationTableService;
    @Autowired
    private IThirdPartyPaymentService thirdPartyPaymentService;
    @Autowired
    private IMistakeService mistakeService;
    @Autowired
    private IPaymentHandler paymentHandler;
    @Autowired
    private GrayVersionConfig grayVersionConfig;
    @Resource
    private ExtCmCustomerSecondLevelMapper extCmCustomerSecondLevelMapper;
    @Resource
    private ExtTlThirdPartyPaymentMapper extTlThirdPartyPaymentMapper;

    @Override
    public TlThirdPartyPayment dealFilePre(TlFilePaymentLog paymentLog) throws TxnBizException {
        String loanId = paymentLog.getLoanId();
        AmLoanAccountInfo loan = extAmLoanAccountInfoMapper.selectByLoanIdForBatch(loanId);
        if(null == loan){
            return null;
        }

        TlThirdPartyPayment partyPayment = extTlThirdPartyPaymentMapper.selectByPayId(paymentLog.getTradeSeqNo(),loan.getCustomerId(),loan.getTenantId());
        if(null != partyPayment){
            return null;
        }

        Date bussinessDate = organizationTableService.findByOrgIdForBatch(TransBizConstant.DEFAULT_ORG_ID).getNextProcessingDate();
        TlThirdPartyPayment tlThirdPartyPayment = thirdPartyPaymentService.generateThirdLog(paymentLog,loan,bussinessDate);
        return tlThirdPartyPayment;
    }


    @Override
    public FilePaymentSaveBean dealFilePay(TlThirdPartyPayment thirdPartyPayment) throws TxnBizException {
        AmLoanAccountInfo loan = extAmLoanAccountInfoMapper.selectByLoanIdForBatch(thirdPartyPayment.getLoanId());
        Date bussinessDate = organizationTableService.findByOrgIdForBatch(TransBizConstant.DEFAULT_ORG_ID).getNextProcessingDate();
        if(TransBizConstant.REPAYMENT_TYPE_PRETERMINTION.equals(thirdPartyPayment.getPaymentType())){
            return this.dealPayOff(thirdPartyPayment,loan,bussinessDate);
        }else{//正常，逾期还款
            return this.dealPay(thirdPartyPayment,loan,bussinessDate);
        }
    }


    /**
     * 处理提前结清
     * @param thirdPartyPayment
     * @param loan
     * @param bussinessDate
     * @return
     * @throws TxnBizException
     */
    private FilePaymentSaveBean dealPayOff(TlThirdPartyPayment thirdPartyPayment, AmLoanAccountInfo loan,Date bussinessDate) throws TxnBizException {
        FilePaymentSaveBean filePaymentSaveBean = new FilePaymentSaveBean();
        DebtBean debtBean = debtCalculationService.getBalance(loan,bussinessDate,null, null,
                null, false);
        //还款金额
        BigDecimal repayAmt = thirdPartyPayment.getAmount();
        //欠款金额
        BigDecimal toatalAmount = debtBean.getTotalAmount();
        //如果金额不等写入差错
        if(repayAmt.compareTo(toatalAmount) != 0){
            TlThirdPartyPayment updatePayment = new TlThirdPartyPayment();
            updatePayment.setId(thirdPartyPayment.getId());
            updatePayment.setSumStatus(TransBizConstant.PAYMENT_LOG_SUM_STATUS_F);
            updatePayment.setDescription("还款金额"+repayAmt+"不等于欠款金额"+toatalAmount);
            filePaymentSaveBean.setTlThirdPartyPayment(updatePayment);
            return filePaymentSaveBean;
        }

        boolean sucess = thirdPartyPaymentService.fileThirdPartyAllocation(filePaymentSaveBean,thirdPartyPayment);
        //还款分配未成功
        if(!sucess){
            return filePaymentSaveBean;
        }

        //发送api mq消息 生成结清证明
        try {
            AmLoanAccountInfo amLoanAccountInfo = filePaymentSaveBean.getPaymentSaveBean().getUpdateLoanList().get(0);
            AmLoanMainInfo amLoanMainInfo = filePaymentSaveBean.getPaymentSaveBean().getAmLoanMainInfoList().get(0);
            PayoffProveMessage message = new PayoffProveMessage();
            String customerId = thirdPartyPayment.getCustomerId();
            String channel = thirdPartyPayment.getChannel();
            String tenantId = thirdPartyPayment.getTenantId();
            String loanId = thirdPartyPayment.getLoanId();
            message.setChannelNo(channel);
            message.setTenantId(tenantId);
            message.setLoanNo(loanId);
            message.setLoanDate(amLoanMainInfo.getPostingDate());
            message.setPayoffDate(amLoanAccountInfo.getPayoffDate());
            message.setTotalTenor(amLoanMainInfo.getTotalTenor());
            message.setLoanAmount(amLoanMainInfo.getLoanAmount());
            CmCustomerSecondLevel secondLevel = extCmCustomerSecondLevelMapper.selectByCustomerIdAndChannel(customerId,channel,tenantId);
            message.setUserId(secondLevel.getUserId());
            paymentHandler.sendMqPaymentLog(TransBizConstant.MQ_PAYOFF_PROVE_TOPIC + grayVersionConfig.getCurrentVersion(), message);
        } catch (Exception e) {
            logger.error("提前结清证明发送mq异常:", e);
            TlMistakeLog mistakeLog = mistakeService.buildMistakeLog(thirdPartyPayment, bussinessDate);
            mistakeLog.setMisType(TransBizConstant.MIS_TYPE_8);
            filePaymentSaveBean.setMistakeLog(mistakeLog);
        }
        return filePaymentSaveBean;

    }

    /**
     * 处理正常还款逾期还款
     * @param thirdPartyPayment
     * @param loan
     * @param bussinessDate
     * @return
     * @throws TxnBizException
     */
    private FilePaymentSaveBean dealPay(TlThirdPartyPayment thirdPartyPayment, AmLoanAccountInfo loan,Date bussinessDate) throws TxnBizException {
        FilePaymentSaveBean filePaymentSaveBean = new FilePaymentSaveBean();

        DebtBean debtBean = debtCalculationService.getBalance(loan,bussinessDate,null, true,
                true, null);
        //还款金额
        BigDecimal repayAmt = thirdPartyPayment.getAmount();
        //欠款金额
        BigDecimal toatalAmount = debtBean.getTotalAmount();
        //如果还款金额大于欠款金额入差错
        if(repayAmt.compareTo(toatalAmount) > 0){
            TlThirdPartyPayment updatePayment = new TlThirdPartyPayment();
            updatePayment.setId(thirdPartyPayment.getId());
            updatePayment.setSumStatus(TransBizConstant.PAYMENT_LOG_SUM_STATUS_F);
            updatePayment.setDescription("还款金额"+repayAmt+"大于欠款金额"+toatalAmount);
            filePaymentSaveBean.setTlThirdPartyPayment(updatePayment);
            return filePaymentSaveBean;
        }

        thirdPartyPaymentService.fileThirdPartyAllocation(filePaymentSaveBean,thirdPartyPayment);
        return filePaymentSaveBean;
    }
}
